package tech.hdis.framework.utils.async;

import lombok.NonNull;

import java.util.concurrent.*;

/**
 * 令牌桶算法异步处理
 *
 * @author 黄志文
 */
public abstract class BaseAsyncHandler<E> implements Runnable {

    /**
     * 每次运行的线程个数
     */
    private final Integer runTimes;
    /**
     * 阻塞队列元素最低执行个数
     */
    private final Integer count;
    /**
     * 阻塞队列
     */
    protected BlockingQueue<E> blockingQueue;
    /**
     * 连接池大小
     */
    private ExecutorService executorService;

    public BaseAsyncHandler(@NonNull BlockingQueue<E> blockingQueue) {
        this(blockingQueue, 1, 1, 1);
    }

    /**
     * 异步化处理
     *
     * @param blockingQueue 阻塞队列
     * @param pool          连接池大小
     * @param runTimes      每次运行的线程个数
     * @param count         阻塞队列元素最低执行个数
     */
    public BaseAsyncHandler(@NonNull BlockingQueue<E> blockingQueue, @NonNull Integer pool, @NonNull Integer runTimes, @NonNull Integer count) {
        executorService = new ThreadPoolExecutor(pool, pool, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<>());
        this.blockingQueue = blockingQueue;
        this.runTimes = runTimes;
        this.count = count;
    }

    public void execute() {
        if (blockingQueue.size() < count) {
            return;
        }
        for (int i = 0; i < runTimes; i++) {
            executorService.execute(this);
        }
    }

}